// Array数组
// 灵活类型,可以在数组中添加任意类型数据
// 动态数组,数组长度随时变化


// 1.创建数组
// (1)构造函数
var arr=new Array(3);
var arr=new Array(1,"2",4);
// 调用构造函数,可以传递参数,单一数字为数组长度,多个参数为数组的项
// (2)字面量
var arr=[];
var arr=[1,"2",,3];
// (3)静态方法
Array.from();
// 参数为任何具有可迭代性的对象:
// 迭代器对象;映射集合;字符串;若干参数项
// 为对象数组时,对数组进行弱复制
// 具有索引以及长度属性的一般对象
Array.of(1,2,"3");
// 若干参数项创建数组


// 2.数组空位
var arr=[1,,"2",,];
// 两,间的为数组空位,占据位置,值为undefined


// 3.数组索引与长度
arr[0];arr[1];arr[length-1];
arr[0]=2;
// 通过中括号加数组索引来访问数组项,可以进行修改,添加操作
arr.length;
arr[length]=6;
// 数组的长度属性,可以通过长度属性进行操作数组项


// 4.数组迭代器方法
// 数组的迭代器方法返回值为一迭代器对象,可以由Array.from()进行创建新数组
arr.keys();
// 返回数组索引迭代器
arr.values();
// 返回数组项值迭代器
arr.entries();
// 返回数组的索引-值的键值对迭代器
// 通过for-of循环利用[idex,element]进行解构


// 5.数组复制填充方法=>对原数组进行修改
arr.fill("2",0,4);
// 返回值是修改后的数组
// 第一个参数为填充的内容,第二个参数为开始索引,第三个参数为结束索引
// 在开始索引和结束索引的前闭后开范围内将数组项修改为填充内容
// 2,3参数相反时忽略,负数则从后向前
arr.copyWithin(2,3,4);
// 返回值是修改后的数组
// 第一个参数为当前插入位置,第二个参数为开始索引,第三个参数为结束索引
// 复制开始索引到结束索引的前闭后开区间,在插入位置处修改复制数组长度的数组项
// 2,3参数相反时忽略,负数则从后向前


// 6.数组转化方法=>不修改原数组
arr.valueOf();
// 返回数组本身
arr.toString();
arr.toLocaleString();
// 对数组每一项调用对应方法,转化为字符串后,再拼串成逗号分割的字符串
arr.join("/");
// 将数组转化为用参数字符分割的字符串

// 7.栈方法=>原字符串修改
// 将数组视为栈数据结构,后进先出,从后方添加数据,从前方取出数据
arr.push(3)
// 在数组后方添加参数数据项,返回修改后的数组长度
arr.pop();
// 返回从数组后方取出的数据项


// 8.队列方法=>原数组修改
// 将数组视为队列数据结构,先进先出,从后方添加数据,从前方取出数据
arr.shift();
// 后方添加数据已有push()方法
// 返回从数组前方取出的数据项
arr.unshift(2);
// 为实现反向队列,从后方取出,从前方添加
// 后方取出已有pop()方法
// 在数组前方添加参数数据项,返回修改后的数组长度


// 9.检验数组
arr instanceof Array;
// 对于单一全局对象,选用instanceof操作符
Array.isArray(arr);
// 对于多个全局对象,不同全局作用域中的Array引用类型不一致
// 选用Array.isArray()方法检验


// 10.数组排序=>原数组修改
arr.reverse();
// 将原数组进行颠倒，返回值为颠倒后的数组
arr.sort(rank);
// 将原数组按排序函数进行排序，返回值为排序后的数组
// 默认为将数组中的每个元素调用toString()方法，进行升序排列
function rank(a,b){
    if(a>b){return -1}
    else if(a=b){return 0}
    else{return 1}
}
// 参数可选排序函数，对数组中两两元素调用排序函数进行排序
// 排序函数具有两个参数
// 第一个参数排在第二个参数前面时，排序函数返回-1
// 第一个参数和第二个参数相等时，排序函数返回0
// 第一个参数排在第二个参数后面时，排序函数返回1


// 11.操作数组
arr.concat("1",[1,2,3]);
// 返回值为将原数组与参数拼接后的新数组
// 默认具有数组扁平化操作
let arr1=[1,3,4];
arr1[Symbol.isConcatSpreadable]=false;
arr.concat(arr1);
// 可以将参数数组的[Symbol.isConcatSpreadable]属性设置为false，不进行扁平化
// 在拼接类数组对象时，也可以将对象的[Symbol.isConcatSpreadable]属性设置为true，进行扁平化

arr.slice(0,3);
// 第一个参数为复制开始位置，第二个参数为复制结束位置
// 返回值为从复制开始位置到复制结束位置的新数组

arr.splice(1,2,4,"5");
// 第一个参数为删除开始位置，第二个参数为需删除的元素，后续参数为从开始位置进行插入的元素
// 返回值为包含删除元素的数组


// 12.搜索数组
// 严格模式,判断条件为===
arr.indexOf("3",1);
arr.lastIndexOf(4,0);
// 第一个参数为需搜索的元素，第二个参数为搜索起始位置
// 搜索元素是否在数组中，搜素到后停止，返回搜索到的元素索引，未找到返回-1
// 方向不同
arr.includes("2",1);
// 第一个参数为需搜索的元素，第二个参数为搜索起始位置
// 搜索元素是否在数组中，搜素到后停止，返回值为布尔值

// 断言函数
arr.find(duanyan);
arr.findIndex(duanyan);
// 第一个参数为断言函数，第二个参数为指定断言函数中this的值
// 对数组每个元素调用断言函数，当断言函数返回值为true时，判断为匹配项，停止搜索
// 分别返回对应元素或对应元素的索引
function duanyan(element,index,Array){
    return element=1;
}
// 断言函数可选参数为数组元素，数组元素索引，搜索数组本身
// 返回值为一布尔值，为true时为匹配项，在断言函数中可以对元素，索引，数组进行相关操作


// 13.归并数组
arr.reduce(guibing,0);
arr.reduceRight(guibing);
// 第一个参数为归并函数，第二个参数为指定归并值的初始值，未指定时归并初始值为数组起始项，且从第二项开始归并
// 对数组中每个元素调用归并函数，归并函数返回一个归并值，最终返回一个归并值在整个数组中归并的结果
// 方向不同
function guibing(pre,cur,index,Array){
    return pre+index+cur;
}
// 归并函数可选四个参数，当前归并值，当前数组元素，数组元素索引，操作数组
// 可以在归并函数内，对数组元素，数组，索引与当前归并值进行操作
// 归并函数返回值为下一步归并的归并值


// 14.迭代数组=>不对元素组进行修改
// 第一个参数为调用函数，第二个参数可以指定调用函数的this值
arr.every(func);
arr.some(func);
// 对每个数组元素进行调用函数，调用函数返回值全为true，every()返回值为true；调用函数返回值存在，some()返回值为true
arr.filter(func);
// 对每个数组元素调用函数，将调用函数返回值为true的元素记录，返回一个记录元素组成的新数组
function func(element,index,Array){
    return element>1;
}
// 调用函数返回值为布尔值，调用函数可选参数为数组元素，数组索引，操作数组；
// 调用函数内部可以对以上参数进行相关操作

arr.map(func2);
// 对每个数组元素调用函数，返回一个指行调用函数之后的新数组
function func2(element,index,Array){
    return element=element+index;
}
// map()中的调用函数将所有返回值记录，返回一个返回值数组

arr.forEach(func2);
// 该方法没有返回值，本质上类似于遍历每个数组元素
